package com.ltv.xiangqiplugin.views;

import java.awt.GridBagConstraints;
import java.awt.GridBagLayout;
import java.util.Vector;

import javax.swing.JApplet;
import javax.swing.SwingUtilities;

import com.ltv.xiangqiplugin.controllers.BoardSizeControl;
import com.ltv.xiangqiplugin.controllers.GameActionControl;
import com.ltv.xiangqiplugin.models.BoardSizeEnum;
import com.ltv.xiangqiplugin.models.Game;
import com.ltv.xiangqiplugin.models.MoveStack;
import com.ltv.xiangqiplugin.models.PositionStack;
import com.ltv.xiangqiplugin.utils.MoveUtils;

@SuppressWarnings("serial")
public class ChessApp extends JApplet {
	private static Vector<String> bufferedMoves;
	private static Vector<String> bufferedVnMoves;
	private static Vector<String> bufferedPositions;
	private static int bufferedIndex;
	
	private String initPosition;
	private String moveList;
	private Integer startIndex;
	
	private boolean started;
	
	@Override
	public void init() {
		initParameters();
	}
	
	private void initParameters() {
		initPosition = this.getParameter("initPosition");
	    moveList = this.getParameter("moveList");
	    
	    startIndex = 0;
	    try {
	    	startIndex = Integer.parseInt(this.getParameter("startIndex"));
	    } catch (Exception e) {
	    	startIndex = 0;
		}
	}
	
	private void createGUI() throws Exception {
		this.getContentPane().setLayout(new GridBagLayout());
		
		Game game = new Game();
		BoardView.defaultBoardView().setGame(game);
		
	    if (initPosition != null && !initPosition.trim().equals("")) {
	    	try {
	    		game.setPosition(initPosition);
			} catch (Exception e) {
				// Do nothing
			}
	    }
	    
	    String boardSize = this.getParameter("boardSize");
	    if (boardSize != null && !boardSize.trim().equals("")) {
	    	if (boardSize.equalsIgnoreCase(BoardSizeEnum.SMALL.toString())) {
	    		BoardSizeControl.getInstance().getBoardSize().setSize(BoardSizeEnum.SMALL);
	    	} else if (boardSize.equalsIgnoreCase(BoardSizeEnum.MEDIUM.toString())) {
	    		BoardSizeControl.getInstance().getBoardSize().setSize(BoardSizeEnum.MEDIUM);
	    	} else if (boardSize.equalsIgnoreCase(BoardSizeEnum.LARGE.toString())) {
	    		BoardSizeControl.getInstance().getBoardSize().setSize(BoardSizeEnum.LARGE);
	    	} else {
	    		BoardSizeControl.getInstance().getBoardSize().setSize(BoardSizeEnum.MEDIUM);
	    	}
	    } else {
	    	BoardSizeControl.getInstance().getBoardSize().setSize(BoardSizeEnum.MEDIUM);
	    }
	    
	    
	    if (moveList != null && !moveList.trim().equals("")) {
		    String moves[] = moveList.toLowerCase().split("\\+");
		    
		    for (String move : moves) {
		    	String vnMove = MoveUtils.getVnMove(move, game);
		    	if (game.move(move, false)) {
			    	PositionStack.getInstance().addPostion(game.getPosition());
					MoveStack.getInstance().addMove(move);
					MoveStack.getInstance().addVnMove(vnMove);
		    	} else {
		    		break;
		    	}
		    }
		    MoveStack.getInstance().notifyObservers(true);
	    }
	    
	    PositionStack.getInstance().notifyObservers();
	    
	    if (startIndex > 0 && startIndex < PositionStack.getInstance().getPositions().size()) {
		    startIndex = PositionStack.getInstance().getPositions().size() - startIndex - 1;
		    
		    PositionStack.getInstance().setIndex(startIndex);
		    MoveStack.getInstance().setIndex(startIndex);
		    
		    PositionStack.getInstance().notifyObservers();
		    MoveStack.getInstance().notifyObservers(false);
	    } else {
	    	PositionStack.getInstance().first();
	    	MoveStack.getInstance().first();
	    }
	    
	    bufferedPositions = new Vector<String>();
	    for (String position : PositionStack.getInstance().getPositions()) {
	    	bufferedPositions.add(position);
	    }
	    
	    bufferedMoves = new Vector<String>();
	    for (String move : MoveStack.getInstance().getMoves()) {
	    	bufferedMoves.add(move);
	    }
	    
	    bufferedVnMoves = new Vector<String>();
	    for (String vnMove : MoveStack.getInstance().getVnMoves()) {
	    	bufferedVnMoves.add(vnMove);
	    }
	    
	    bufferedIndex = 0;
	    
		GridBagConstraints constrs = new GridBagConstraints();
		
		getContentPane().add(BoardView.defaultBoardView());
		
//		if (false) {
			constrs.fill = GridBagConstraints.BOTH;
		    constrs.gridwidth = 1;
		    constrs.gridheight = 1;
		    constrs.gridx = 0;
		    this.getContentPane().add(GameActionView.getInstance(), constrs);
//		}
	    
	    constrs.fill = GridBagConstraints.BOTH;
		constrs.weightx = 1.0;
	    constrs.gridx = GridBagConstraints.RELATIVE;
	    constrs.gridheight = 1;
	    constrs.fill = GridBagConstraints.BOTH;
	    constrs.gridwidth = GridBagConstraints.REMAINDER;
	    this.getContentPane().add(MoveStackView.getInstance(), constrs);
	    
	    if (true) {
//	    	BoardView.defaultBoardView().removeMouseListener();
	    }
	    
	}
	
	
	
	@Override
	public void start() {
		if (!started) {
			//Execute a job on the event-dispatching thread; creating this applet's GUI.
	        try {
	            SwingUtilities.invokeAndWait(new Runnable() {
	                public void run() {
	                    try {
							createGUI();
						} catch (Exception e) {
							e.printStackTrace();
						}
	                }
	            });
	        } catch (Exception e) { 
	            e.printStackTrace();
	        }
	        started = true;
		}
	}

	public static Vector<String> getBufferedMoves() {
		Vector<String> ret = new Vector<String>();
	    for (String move : bufferedMoves) {
	    	ret.add(move);
	    }
	    
		return ret;
	}
	
	public static Vector<String> getBufferedVnMoves() {
		Vector<String> ret = new Vector<String>();
	    for (String vnMove : bufferedVnMoves) {
	    	ret.add(vnMove);
	    }
	    
		return ret;
	}

	public static Vector<String> getBufferedPositions() {
		Vector<String> ret = new Vector<String>();
	    for (String position : bufferedPositions) {
	    	ret.add(position);
	    }
	    
		return ret;
	}

	public static int getBufferedIndex() {
		return bufferedIndex;
	}

	public static void setBufferedIndex(int bufferedIndex) {
		ChessApp.bufferedIndex = bufferedIndex;
	}
	
}
